<?php

namespace app\api\controller\v1;

use think\Controller;
use think\Request;
use app\api\controller\v1\Common;
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
use PHPMailer\PHPMailer\Exception;

class Code extends Common {
 
    protected $request;
    public function __construct(Request $request) {
        //parent::initialize();
        $this->request = $request;
    }

    /**
     * 获取验证码
     *
     * @return \think\Response
     */
    public function get_code() {
        $username = $this->request->param('username');
        $exist = $this->request->param('is_exist');
        $username_type = $this->check_username($username);
        switch ($username_type) {
            case 'phone':
                $this->get_code_by_username($username, $username_type, $exist);
                break;
            case 'email':
                $this->get_code_by_username($username, $username_type, $exist);
                break;
            default:
                break;
        }
    }

    /**
     * 通过手机/邮箱获取验证码
     * @param string $username 手机号/邮箱
     * @param int $exist 手机/邮箱号是否存在数据库中，1存在0不存在
     * @return json api返回的json数据
     */
    public function get_code_by_username($username, $type, $exist) {
        /* 处理用户名中的.符号，在thinkphp中.代表二位数组 */
        $session_username = str_replace(".","_",$username);
        
        $type_name = $type == 'phone' ? '手机号' : '邮箱';
        /* 检测手机/邮箱号是否存在 */
        $this->check_exist($username, $type, $exist);
        /* 检查验证码请求频率，30秒一次 */
        if (session('?' . $session_username . '_last_send_time')) {
            if (time() - session($session_username . '_last_send_time') < 1) {
                $this->msg(400, $type_name . '验证码，每30秒只能请求一次！');
            }
        }
        /* 生成验证码 */
        echo $code = $this->make_code(6);
        /* 使用session存储验证码，方便比对，md5加密 */
        $md5_code = md5($username . '-' . md5($code));
        session($session_username . '_code', $md5_code);
        /* 使用session存储验证码发送时间 */
        session($session_username . '_last_send_time', time());
        /* 发送验证码 */
        if ($type == 'phone') {
//            $this->send_code_to_phone($username, $code);
            $this->msg(200,'发送手机验证码');
        } else {
            $this->send_code_to_email($username, $code);
        }
    }

    /**
     * 生成随机数字验证码
     * @param int $len 验证码长度
     * @return string 输出验证码
     */
    public function make_code($len) {
        $max = pow(10, $len) - 1;
        $min = pow(10, $len - 1);
        return rand($min, $max);
    }

    public function send_code_to_phone($username, $code) {
        //url参数
        function warp_query($params) {
            $params['accesskey'] = '大白兔奶糖';
            $params['secret'] = '49AC61771E52B6A2A5F0261B6AF3';
            return $params;
        }
        //发送验证码
        function send_request($url, $params = '') {
            $headers=array(
                "Content-Type:application/x-www-form-urlencoded",
            );

            if (is_array($params))
            {
                $params = http_build_query($params, null, '&');
            }

            $ch = curl_init ();
            curl_setopt ( $ch, CURLOPT_URL, $url );
            curl_setopt ( $ch, CURLOPT_RETURNTRANSFER, 1 );
            curl_setopt ( $ch, CURLOPT_CUSTOMREQUEST, 'POST');
            curl_setopt ( $ch, CURLOPT_POSTFIELDS, $params);
            curl_setopt ( $ch, CURLOPT_HTTPHEADER, $headers );
            curl_setopt ( $ch, CURLOPT_TIMEOUT, 60 );
            $result = curl_exec ( $ch );
            curl_close ( $ch );

            return json_decode($result);
        }
        //发送验证码接口
        function send_verify_code($mobile, $content, $sign, $templateId) {
            $api_url = "http://api.1cloudsp.com/api/v2/single_send";
            $params = warp_query([
                'mobile'=>$mobile,
                'content'=>$content,
                'sign'=>$sign,
                'templateId'=>$templateId]);
            return send_request($api_url, $params);
        }
        return send_verify_code($username,$code,'【测试签名】','85984');
    }
    
    /**
     * 向邮箱发送验证码
     * @param string $email 目标邮箱
     * @param int $code 验证码
     * @return json 返回消息
     */

    public function send_code_to_email($email, $code) {
        $mail = new PHPMailer(true);
        try {
            //服务器配置
            //$mail->SMTPDebug = SMTP::DEBUG_SERVER;                      //是否开启发送调式
            $mail->isSMTP();                                            //设置发送协议是smtp
            $mail->Host = 'smtp.qq.com';                     //SMTP服务器
            $mail->SMTPAuth = true;                                   //允许 SMTP 认证
            $mail->Username = '8373499@qq.com';                     //SMTP 用户名  即邮箱的用户名
            $mail->Password = 'vimbpxucnfrnbigd';                               //SMTP 密码  部分邮箱是授权码(例如163邮箱)
            $mail->SMTPSecure = PHPMailer::ENCRYPTION_SMTPS;            //允许 TLS 或者ssl协议 这里调用TLS
            $mail->Port = 465;                                    //服务器端口 25 或者465 具体要看邮箱服务器支持
            //Recipients
            $mail->setFrom('8373499@qq.com', '接口测试');         //发件人
            $mail->addAddress($email, 'test');     //收件人
            //$mail->addAddress('ellen@example.com');               //可添加多个收件人
            $mail->addReplyTo('8373499@qq.com', $email.'回复消息');   //回复的时候回复给哪个邮箱 建议和发件人一致
            //$mail->addCC('cc@example.com');                         //抄送
            //$mail->addBCC('bcc@example.com');                       //密送

            //发送附件
            //$mail->addAttachment('/var/tmp/file.tar.gz');         //添加附件
            //$mail->addAttachment('/tmp/image.jpg', 'new.jpg');    //发送附件并且重命名
            //Content
            $mail->isHTML(true);                                  //是否以HTML文档格式发送  发送后客户端可直接显示对应HTML内容
            $mail->Subject = '这里是邮件标题'.date('Y-m-d H:i:s');
            $mail->Body = "<h1>您好，{$email}。欢迎您注册本网站。</h1>这是测试邮件，您的验证码是<font color=red>".$code.'</font>。验证码的有效期为1分钟，本邮件请勿回复！'.date('Y-m-d H:i:s');
            $mail->AltBody = '如果邮件客户端不支持HTML则显示此内容';
            
            $mail->send();
            $this->msg(200,'验证码发送成功。');
        } catch (Exception $e) {
            $this->msg(400,"邮件发送失败！{$mail->ErrorInfo}");
        }
    }

}
